15685
8484
Mám seznam časů v sekundách, jako například:
L = [0,10218048, 1,20851996, 1,46800021, 1,73429061, 2,71525848,
3.14781922, 3.63637958, 5.11147358, 5.97497864, 6.35469013,
6.80623747, 6.99571917, 7.65215123, 7.86108352, 8.52988247,
8.83068894, 10.07690977, 11.53867284, 12.01214112, 12.13307653]
Pro každé okno o délce 2 sekund počínaje druhou hranicí bych chtěl vypsat seznam všech časů, které spadají do 2sekundového okna. Takže pro výše uvedený příklad by to bylo:
[0,10218048, 1,20851996, 1,46800021, 1,73429061]
[1.20851996, 1.46800021, 1.73429061, 2.71525848]
[2.71525848, 3.14781922, 3.63637958]
[3.14781922, 3.63637958]
[5.11147358, 5.97497864]
[5.11147358, 5.97497864, 6.35469013, 6.80623747, 6.99571917]
[6.35469013, 6.80623747, 6.99571917, 7.65215123, 7.86108352]
[7.65215123, 7.86108352, 8.52988247, 8.83068894]
[8,52988247, 8,83068894]
[10.07690977]
[10.07690977, 11.5386728]
[11.5386728, 12.01214112, 12.13307653]
[12.01214112, 12.13307653]
Obecně se délka okna může lišit od 2.
Jak to můžete udělat? 
Myslím, že jste mysleli přírůstek založený na „Pro každé okno o délce 2 sekund počínaje druhou hranicí“ a nepřekrývající se. Pro dvousekundové intervaly je to stejné, ale protože chcete změnit délku, překrytí jedné sekundy by bylo 0-3, 2-5, 4-7, ale přírůstek by znamenal 0-3, 1-4, 2- 5. Bylo však zajímavé zjistit řešení pro oba případy.
Za předpokladu, že L je seřazeno a všechny prvky jsou kladné a všechny druhé intervaly začínají celými čísly, můžeme použít tuto metodu:
import matematiky
ze sbírek importovat defaultdict
L = [0,10218048, 1,20851996, 1,46800021, 1,73429061, 2,71525848,
3.14781922, 3.63637958, 5.11147358, 5.97497864, 6.35469013,
6.80623747, 6.99571917, 7.65215123, 7.86108352, 8.52988247,
8.83068894, 10.07690977, 11.53867284, 12.01214112, 12.13307653]
my_ranges = defaultdict (seznam)
interval_width = 2
pro x v L:
upper_bound = math.ceil (x)
lower_bound = upper_bound - interval_width
lower_bound = max (0, lower_bound)
pro y v rozsahu (lower_bound, upper_bound):
my_ranges [y] .append (x)
pro seřazené (my_ranges):
tisk (my_ranges [a])
Nevím, jestli chcete zjistit, jestli existují nějaké prázdné rozsahy. Ale pokud chcete, vytiskne defaultdict prázdné rozsahy. Použijte tento řádek namísto „pro seřazené“:
pro rozsah v rozsahu (min (my_ranges), max (my_ranges) + 1):
Pokud jste chtěli rozsahy 0-3, 2-5, 4-7, toto funguje:
import matematiky
ze sbírek importovat defaultdict
L = [0,10218048, 1,20851996, 1,46800021, 1,73429061, 2,71525848,
3.14781922, 3.63637958, 5.11147358, 5.97497864, 6.35469013,
6.80623747, 6.99571917, 7.65215123, 7.86108352, 8.52988247,
8.83068894, 10.07690977, 11.53867284, 12.01214112, 12.13307653]
interval_width = 2
my_ranges_2 = defaultdict (seznam)
pro x v L:
určitě_v = (x // (interval_width - 1)) * (interval_width - 1) # nejnižší násobek interval_width pod x bude vždy v
#print ("Přidání", x, "do", určitě_v)
my_ranges_2 [určitě_v] .append (x)
pokud x  = 0: # například pokud je x 2,3 a máme 0,3 2,5 atd ... musíme tento duplicitní případ zachytit. Předpokládám, že délky oken jsou celá čísla, a pokud ne, máme toho mnohem víc, protože číslo může jít do více než jednoho pole. Možná bychom mohli mít while smyčku, zvyšující se o (interval_width - 1)
#print ("++ Přidávání", x, "do", určitě_v - interval_ šířka + 1)
my_ranges_2 [určitě_v - intervalová šířka + 1] .append (x)
pro seřazené (my_ranges_2):
print (a, my_ranges_2 [a])
# print (my_ranges_2 [a])
Mám podezření, že existují některé podrobnosti, které jsem zapomněl, ale doufejme, že můžete podle potřeby twiddle interval_width zajistit, aby můj kód dělal to, co jste doufali, a dejte mi vědět, co přesně potřebujete.
|
Možné řešení, které mohu navrhnout, je „efektivní“ v jistém smyslu, že iteruje pouze jednou přes vstupní data a nemá žádné závislosti. Cena samozřejmě spočívá v tom, že je napsán v čistém pythonu (může existovat více optimalizovaný kód) a že zavádí více sledovacích proměnných, aby se zabránilo opakování (a je tedy méně pythonický).
def sliding_window (data, duration, start = 0, overlap = 1):
výsledek = []
data_idx = 0
result_idx = 0
horní = start + doba trvání
nižší = start
next_lower = horní - překrytí
# vnitřní pomocník k vyplnění prázdných vnitřních seznamů až k našemu bodu vložení a vložení
def pad_and_append (zavináč):
while len (výsledek) <= v:
result.append ([])
výsledek [at] .append (data [data_idx])
# iterace přes vstupní data
while data_idx  a:
pokud x  = l [0]) & (L  = i) & (L